package cn.test.learnkotlin.v1

private class EClassAndObject {

    /**
     * 类定义
     */
    private class Foo {
    }

    /**
     * 空类
     */
    private class Empty

    /**
     * 类中定义成员函数
     */
    private class Foo1 {
        fun foo() {
            print("foo")
        }
    }

    /**
     * 属性定义
     */
    private class Foo2 {
        var name: String = "KK"
        var url = "kkUp.com"
        var city = "SZ"
    }

    private class Person(firstName: String) {

    }

    /**
     * getter 和 setter
     */
    private class Person1(firstName: String) {
        val lastName: String = "Kent"
            get() = field.uppercase()

        var no: Int = 1
            get() = field
            set(value) {
                if (value < 10) {
                    field = value
                } else {
                    field = 1
                }
            }

        var height: Float = 145.4f
            private set
    }

    /**
     * lateinit
     */
    private class LateInitField {
        lateinit var person: Person1

        //基本类型不支持lateinit
        //lateinit var aInt: Int

        init {
            person = Person1("up")
        }
    }

    private fun fooLateInit() {
        print(LateInitField().person)
    }

    private class Person2 constructor(name: String) {
        init {
            print("name is $name")
        }
    }

    private class Person3(val firstName: String, val lastName: String) {
        private fun foo() {
            firstName
        }
    }

    private class Runoob(name: String) {
        val url = "runoob.com"
        val country = "CN"
        val siteName = name

        init {
            print("初始化网站名：$name")
        }
    }

    private class Person4 {
        val children: ArrayList<Person4> = ArrayList()

        constructor(parent: Person4) {
            parent.children.add(this)
        }
    }

    private class Person5(val name: String) {
        constructor(name: String, age: Int) : this(name) {
        }
    }

    /**
     * 私有构造函数
     */
    private class NoInstance private constructor() {
    }

    open class Base {
        open fun f() {}
    }

    abstract class Derived : Base() {
        abstract override fun f()
    }

    private class Outer {
        private val bar: Int = 1

        var v = "value outside"

        /**
         * 嵌套类
         */
        class Nested {
            fun foo() = 2
            //fun foo1() = bar//无法访问bar
        }

        /**
         * 内部类
         */
        inner class Inner {
            fun foo() = bar
            fun innerTest() {
                var o = this@Outer
                print("Access for Outer value v:$v")
            }
        }
    }

    /**
     * 嵌套类
     */
    private fun fooNestedClass() {
        val foo: Int = Outer.Nested().foo()
    }

    /**
     * 内部类
     */
    private fun fooInnerClass() {
        Outer().Inner().foo()
        Outer().Inner().innerTest()
    }

    private class Foo3 {
        var v = "成员属性"

        fun setInterface(i: FooInterface) {
            i.test()
        }

        interface FooInterface {
            fun test()
        }
    }

    /**
     * 匿名内部类
     */
    private fun fooAnonymous() {
        Foo3().setInterface(object : Foo3.FooInterface {
            override fun test() {
                println("对象表达式创建匿名内部类的实例")
            }
        })
    }

    fun main() {
        fooAnonymous()
    }
}

fun main() {
    EClassAndObject().main()
}